package org.rcy.framework.data.util;

import org.rcy.framework.api.entity.EnhancedPagableCondition;

import java.util.ArrayList;
import java.util.List;

public class PageQueryUtil<T extends EnhancedPagableCondition,V> {
    //开启使用
    Boolean open = Boolean.FALSE;
    //查询偏移量
    Integer originalOffset;
    //查询条数
    Integer originalPageSize;
    //累计数
    Integer cumulativeCount = 0;
    //查询数据范围起始值
    Integer queryStart = 1;
    //是否继续查询
    Boolean continueQuery = Boolean.TRUE;
    //是否最后一次查询
    Boolean isLastQuery = Boolean.FALSE;

    List<V> data = new ArrayList<>();

    Integer offset;


    public void init(Integer originalOffset,Integer originalPageSize){
        this.originalOffset = originalOffset;
        this.originalPageSize = originalPageSize;
        this.open = true;
    }
    public void addAll(List<V> data){
        this.data.addAll(data);
    }

    public Boolean isContinueQuery(Long count,T query){
        if (!open){
            throw new RuntimeException("not pen page query");
        }

        if (isLastQuery){
            return Boolean.FALSE;
        }

        if(data.size() >= originalPageSize) {
            return false;
        }

        //需要查询数据范围为集合 ab [a,b]
        int a = originalOffset + 1;
        int b = originalOffset + originalPageSize;

        //本次查询数据范围为集合 cd [c,d]
        int c = queryStart;
        int d = queryStart + count.intValue() - 1;
        //下个查询数据集合开始值
        queryStart = d + 1;

        // 本次是否需要查询
        continueQuery = !(d < a || c > b);
        if (!continueQuery) {
            return Boolean.FALSE;
        }

        //本次是否需要查询数据  求 cd 与 ab交集 ef [] ，得
        int e = c <= a ? a : c;
        int f = d >= b ? b : d;

        //本次查询数
        int queryCount = f - e + 1;
        //剩余需要查询数
        int needQueryCount =  originalPageSize - cumulativeCount;
        if (needQueryCount < queryCount){
               queryCount = needQueryCount;
        }

        //累计数添加
        cumulativeCount = cumulativeCount + queryCount;
        //是否最后一次查询
        isLastQuery = cumulativeCount == originalPageSize;

        //设置查询范围
        query.setOffset(e - c);
        query.setPageSize(queryCount);
        query.setOpen(true);
        return continueQuery;
    }

    public Boolean getOpen() {
        return open;
    }

    public void setOpen(Boolean open) {
        this.open = open;
    }

    public List<V> getData() {
        return data;
    }

    public void setData(List<V> data) {
        this.data = data;
    }
}
